ROLLBACK; BEGIN; CREATE TABLE example_table ( test_column TEXT unique ) ; INSERT INTO example_table VALUES ('abc') ON CONFLICT (test_column) DO NOTHING ; CREATE PROCEDURE example_works ( test_column_in TEXT ) AS $$ #variable_conflict use_variable BEGIN INSERT INTO example_table (test_column) VALUES (test_column_in) ON CONFLICT (test_column) DO NOTHING ; END $$ LANGUAGE plpgsql ; CALL example_works('xyz'); SELECT * FROM example_table ; CREATE PROCEDURE example_breaks ( test_column TEXT -- ^ note: the new declaration name is the same as the column name ) AS $$ #variable_conflict use_variable BEGIN -- ^ normally, name conflicts would be resolved successully this way... INSERT INTO example_table (test_column) -- `variable_conflict` is working here √ VALUES (test_column) -- `variable_conflict` is working here √ ON CONFLICT (test_column) DO NOTHING -- `variable_conflict` is NOT working here X @ `(test_column)` ; END $$ LANGUAGE plpgsql ; CALL example_breaks('qwe'); /* [42P10] ERROR: there is no unique or exclusion constraint matching the ON CONFLICT specification PL/pgSQL function example_breaks(text) line 6 at SQL statement */ ROLLBACK;